package ocumed.applikation.patient;

import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;

import ocumed.applikation.exceptions.NoLandException;
import ocumed.applikation.exceptions.NoOrtException;
import ocumed.applikation.exceptions.PatientAlreadyExistsException;
import ocumed.applikation.exceptions.VersNummerStartsWithZeroException;
import ocumed.applikation.exceptions.VersNummerWrongLengthException;
import ocumed.applikation.exceptions.VersNummerWrongPruefzifferException;
import ocumed.domaene.patientenverwaltung.DLand;
import ocumed.domaene.patientenverwaltung.DOrt;
import ocumed.domaene.patientenverwaltung.DPatient;
import ocumed.persistenz.dao.BenutzerDAO;
import ocumed.persistenz.dao.DAOFactory;
import ocumed.persistenz.dao.LandDAO;
import ocumed.persistenz.dao.OrtDAO;
import ocumed.persistenz.dao.PatientDAO;
import ocumed.persistenz.hibernate.OcBenutzer;
import ocumed.persistenz.hibernate.OcLand;
import ocumed.persistenz.hibernate.OcOrt;
import ocumed.persistenz.hibernate.OcPatient;

public class PatAnlegen {

	private PatientDAO pDAO;
	private BenutzerDAO bDAO;
	private LandDAO lDAO;
	private OrtDAO oDAO;
	private int bestimmterArzt;
	
	/*public static void main(String[] args) {
		PatAnlegen pa = new PatAnlegen();
		
	}*/
	
	public PatAnlegen() {
		bDAO = DAOFactory.get(DAOFactory.RDBMS).getBenutzerDAO();
		pDAO = DAOFactory.get(DAOFactory.RDBMS).getPatientDAO();
		lDAO = DAOFactory.get(DAOFactory.RDBMS).getLandDAO();
		oDAO = DAOFactory.get(DAOFactory.RDBMS).getOrtDAO();

		setBestimmterArzt(bestimmeArztById());
	}

	public void pruefeVersNr(String versNr)
			throws VersNummerWrongLengthException,
			VersNummerStartsWithZeroException,
			VersNummerWrongPruefzifferException, PatientAlreadyExistsException {
		new DPatient(versNr).pruefeVersNr();
		pDAO.start();
		if (versNr.length() != 0 && (pDAO.findByVersNr(versNr) != null)) {
			throw new PatientAlreadyExistsException();
		}
	}

	public boolean neuerPatient(String titel, String vorname, String nachname,
			String geschlecht, Date gebDat, String versNr,
			Boolean besitztEcard, Integer arztId, Integer landId,
			Integer ortId, String adresse, String telefon, String fax,
			String hVorna, String hNachn, String hTelefon, String hVersNr) {

		OcBenutzer ocBenutzerByArztid = null;
		if (arztId != bestimmterArzt) {
			ocBenutzerByArztid = bDAO.findById(arztId);
		} else {
			ocBenutzerByArztid = bDAO.findById(bestimmterArzt);
		}

		Calendar gebDatum = Calendar.getInstance();
		gebDatum.setTime(gebDat);

		char ecard = '\0';
		char geschlechtAbk = '\0';
		String anrede = "";
		if (besitztEcard == true) {
			ecard = PatientDAO.besitztEcard;
		} else {
			ecard = PatientDAO.besitztKeineEcard;
		}
		if (geschlecht.equals("m")) {
			geschlechtAbk = PatientDAO.geschlechtMaennlich;
			anrede = "Herr";
		} else {
			geschlechtAbk = PatientDAO.geschlechtWeiblich;
			anrede = "Frau";
		}

		setBestimmterArzt(arztId);

		lDAO.start();
		OcLand ocLand = lDAO.findById(landId);
		DLand dPatientLand = new DLand(ocLand.getLandname(), ocLand
				.getLandkurzform(), ocLand.getLandid());
		oDAO.start();
		OcOrt ocOrt = null;
		DOrt dPatientOrt = null;
		if (ortId != null) {
			ocOrt = oDAO.findById(ortId);
			dPatientOrt = new DOrt(ocOrt.getOrtid(), ocLand.getLandid(), ocOrt
					.getOrtplz(), ocOrt.getOrtname());
		}

		DPatient dPatient = new DPatient(anrede, titel, vorname, nachname,
				geschlechtAbk, gebDatum, versNr, ecard, arztId, dPatientOrt,
				adresse, telefon, fax, hVorna, hNachn, hTelefon, hVersNr);

		// OcBenutzer ocBenutzerByGeandertvonid = new OcBenutzer(); // TODO

		pDAO.start();
		OcPatient ocPatient = new OcPatient();
		ocPatient.setPatientanrede(anrede);
		ocPatient.setPatientnachname(nachname);
		ocPatient.setPatientvorname(vorname);
		ocPatient.setGeandertam(Calendar.getInstance());
		ocPatient.setOcBenutzerByArztid(ocBenutzerByArztid);
		ocPatient.setOcBenutzerByGeandertvonid(ocBenutzerByArztid);
		ocPatient.setOcOrt(ocOrt);
		ocPatient.setPatientadresse(adresse);
		ocPatient.setPatientgeschlecht(geschlechtAbk);
		ocPatient.setPatientbesitztecard(ecard);
		ocPatient.setPatientfax(fax);
		ocPatient.setPatientgebdatum(gebDatum);
		ocPatient.setPatientgeschlecht(geschlechtAbk);
		ocPatient.setPatientstatus(PatientDAO.typErfasst);
		ocPatient.setPatientsvn(versNr);
		ocPatient.setPatienttel(telefon);

		pDAO.persist(ocPatient);
		pDAO.commit();

		return true;
	}

	private int bestimmeArztById() {
		int anzahlTermine = 2147483647;
		int arztId = -1;
		bDAO.start();
		List<OcBenutzer> arztListe = bDAO.findByGroup(BenutzerDAO.typArzt);
		Iterator<OcBenutzer> iterator = arztListe.iterator();
		OcBenutzer tempArzt = null;

		while (iterator.hasNext()) {
			tempArzt = iterator.next();
			if (anzahlTermine > tempArzt.getOcTermins().size()) {
				anzahlTermine = tempArzt.getOcTermins().size();
				arztId = tempArzt.getBenutzerid();
			}
		}
		return arztId;
	}

	public HashMap<Integer, String> getArztListe() {
		bDAO.start();
		List<OcBenutzer> arztListe = bDAO.findByGroup(BenutzerDAO.typArzt);
		Iterator<OcBenutzer> iterator = arztListe.iterator();
		HashMap<Integer, String> arztList = new HashMap<Integer, String>();
		OcBenutzer tempArzt = null;
		while (iterator.hasNext()) {
			tempArzt = iterator.next();
			arztList.put(tempArzt.getBenutzerid(), tempArzt
					.getBenutzernachname());
		}
		return arztList;
	}

	public HashMap<Integer, String> getLaender() throws NoLandException {
		lDAO.start();
		List<OcLand> laenderListe = lDAO.findAll();
		Iterator<OcLand> iterator = null;
		HashMap<Integer, String> laenderList = null;
		if (laenderListe.isEmpty()) {
			throw new NoLandException();
		} else {
			iterator = laenderListe.iterator();
			laenderList = new HashMap<Integer, String>();
			OcLand tempLand = null;
			while (iterator.hasNext()) {
				tempLand = iterator.next();
				laenderList.put(tempLand.getLandid(), tempLand.getLandname());
			}
		}
		return laenderList;
	}

	public int getVorgeschlagenerArztById() {
		return bestimmterArzt;
	}

	private void setBestimmterArzt(int vorgeschlagenerArztById) {
		this.bestimmterArzt = vorgeschlagenerArztById;
	}

	public HashMap<Integer, String> getOrteByLandId(Integer landId)
			throws NoOrtException {
		oDAO.start();
		List<OcOrt> ortListe = oDAO.findByLand(landId);
		Iterator<OcOrt> iterator = null;
		HashMap<Integer, String> ortList = null;
		if (ortListe.isEmpty()) {
			throw new NoOrtException();
		} else {
			iterator = ortListe.iterator();
			ortList = new HashMap<Integer, String>();
			OcOrt tempOrt = null;
			while (iterator.hasNext()) {
				tempOrt = iterator.next();
				ortList.put(tempOrt.getOrtid(), tempOrt.getOrtname());
			}
		}
		return ortList;
	}
}
